/**
 * Copyright (c) [2025] [AGIROS] 
 * [travoddsgen] is licensed under Mulan PSL v2. 
 * You can use this software according to the terms and conditions of the Mulan PSL v2. 
 * You may obtain a copy of Mulan PSL v2 at: 
 *          http://license.coscl.org.cn/MulanPSL2 
 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, 
 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, 
 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. 
 * See the Mulan PSL v2 for more details.
 */ 

#ifndef defaultvisitor_h__
#define defaultvisitor_h__

#include "AstVisitor.h"
#include "Ast.h"

class DefaultVisitor : public AstVisitor {
public:
    void visit(ASTNode& node) override {
        // Default implementation does nothing
    }

    void visit(ListNode<DefinitionNode*>& node) override {
        for (auto& def : node.nodes_) {
            if (def) {
                def->accept(*this);
            }
        }
    }

    void visit(SpecificationNode& node) override {
        if (node.definitions_) {
            node.definitions_->accept(*this);
        }
    }

    void visit(ModuleDclNode& node) override {
        if (node.definitions_) {
            node.definitions_->accept(*this);
        }
    }

    void visit(ScopedNameNode& node) override {
        // Default implementation does nothing
    }

    void visit(ConstDclNode& node) override {
        if (node.type_) {
            node.type_->accept(*this);
        }
        if (node.expression_) {
            node.expression_->accept(*this);
        }
    }

    void visit(ConstTypeNode& node) override {
        // Default implementation does nothing
    }

    void visit(ConstExprNode& node) override {
        // Default implementation does nothing
    }

    void visit(OrExprNode& node) override {
        if (node.left_) {
            node.left_->accept(*this);
        }
        if (node.right_) {
            node.right_->accept(*this);
        }
    }

    void visit(XorExprNode& node) override {
        if (node.left_) {
            node.left_->accept(*this);
        }
        if (node.right_) {
            node.right_->accept(*this);
        }
    }

    void visit(AndExprNode& node) override {
        if (node.left_) {
            node.left_->accept(*this);
        }
        if (node.right_) {
            node.right_->accept(*this);
        }
    }

    void visit(ShiftExprNode& node) override {
        if (node.left_) {
            node.left_->accept(*this);
        }
        if (node.right_) {
            node.right_->accept(*this);
        }
    }

    void visit(AddExprNode& node) override {
        if (node.left_) {
            node.left_->accept(*this);
        }
        if (node.right_) {
            node.right_->accept(*this);
        }
    }

    void visit(MultExprNode& node) override {
        if (node.left_) {
            node.left_->accept(*this);
        }
        if (node.right_) {
            node.right_->accept(*this);
        }
    }

    void visit(UnaryExprNode& node) override {
        if (node.expr_) {
            node.expr_->accept(*this);
        }
    }

    void visit(PrimaryExprNode& node) override {
        if (node.scopedName_) {
            node.scopedName_->accept(*this);
        }
        if (node.literal_) {
            node.literal_->accept(*this);
        }
        if (node.constExpr_) {
            node.constExpr_->accept(*this);
        }
    }

    void visit(LiteralNode& node) override {
        // Default implementation does nothing
    }

    void visit(PositiveIntConstNode& node) override {
        // Default implementation does nothing
    }

    void visit(TypeDclNode& node) override {
        // Default implementation does nothing
    }

    void visit(ConstrTypeDclNode& node) override {
        // Default implementation does nothing
    }

    void visit(TypeSpecNode& node) override {
        // Default implementation does nothing
    }

    void visit(SimpleTypeSpecNode& node) override {
        // Default implementation does nothing
    }

    void visit(TemplateTypeSpecNode& node) override {
        // Default implementation does nothing
    }

    void visit(BaseTypeNode& node) override {
        // Default implementation does nothing
    }

    void visit(SequenceTypeNode& node) override {
        if (node.type_) {
            node.type_->accept(*this);
        }
        if (node.size_) {
            node.size_->accept(*this);
        }
    }

    void visit(StringTypeNode& node) override {
        if (node.size_) {
            node.size_->accept(*this);
        }
    }

    void visit(WideStringTypeNode& node) override {
        if (node.size_) {
            node.size_->accept(*this);
        }
    }

    void visit(FixedPtTypeNode& node) override {
        if (node.digits_) {
            node.digits_->accept(*this);
        }
        if (node.scale_) {
            node.scale_->accept(*this);
        }
    }

    void visit(MapTypeNode& node) override {
        if (node.keyType_) {
            node.keyType_->accept(*this);
        }
        if (node.valueType_) {
            node.valueType_->accept(*this);
        }
        if (node.size_) {
            node.size_->accept(*this);
        }
    }

    void visit(StructDclNode& node) override {
        // Default implementation does nothing
    }

    void visit(StructDefNode& node) override {
        if (node.annotations_) {
            node.annotations_->accept(*this);
        }
        if (node.members_) {
            node.members_->accept(*this);
        }
    }

    void visit(ListNode<TypeAnnotationNode*>& node) override {
        for (auto& annotation : node.nodes_) {
            if (annotation) {
                annotation->accept(*this);
            }
        }
    }

    void visit(TypeAnnotationNode& node) override {
        if (node.value_) {
            node.value_->accept(*this);
        }
    }

    void visit(MemberNode& node) override {
        if (node.type_) {
            node.type_->accept(*this);
        }
        if (node.arrayDims_) {
            node.arrayDims_->accept(*this);
        }
        if (node.annotations_) {
            node.annotations_->accept(*this);
        }
    }

    void visit(ListNode<MemberNode*>& node) override {
        for (auto& member : node.nodes_) {
            if (member) {
                member->accept(*this);
            }
        }
    }

    void visit(ListNode<FixedArraySizeNode*>& node) override {
        for (auto& fixedArraySize : node.nodes_) {
            if (fixedArraySize) {
                fixedArraySize->accept(*this);
            }
        }
    }

    void visit(FixedArraySizeNode& node) override {
        if (node.size_) {
            node.size_->accept(*this);
        }
    }

    void visit(MemberAnnotationNode& node) override {
        if (node.value_) {
            node.value_->accept(*this);
        }
    }

    void visit(ListNode<MemberAnnotationNode*>& node) override {
        for (auto& annotation : node.nodes_) {
            if (annotation) {
                annotation->accept(*this);
            }
        }
    }

    void visit(StructForwardDclNode& node) override {
        // Default implementation does nothing
    }

    void visit(UnionDclNode& node) override {
        // Default implementation does nothing
    }

    void visit(UnionDefNode& node) override {
        if (node.annotations_) {
            node.annotations_->accept(*this);
        }
        if (node.cases_) {
            node.cases_->accept(*this);
        }
    }

    void visit(SwitchTypeSpecNode& node) override {
        if (node.type_) {
            node.type_->accept(*this);
        }
        if (node.scopedName_) {
            node.scopedName_->accept(*this);
        }
    }

    void visit(ListNode<CaseNode*>& node) override {
        for (auto& caseNode : node.nodes_) {
            if (caseNode) {
                caseNode->accept(*this);
            }
        }
    }

    void visit(CaseNode& node) override {
        if (node.labels_) {
            node.labels_->accept(*this);
        }
        if (node.members_) {
            node.members_->accept(*this);
        }
    }

    void visit(ListNode<CaseLabelNode*>& node) override {
        for (auto& label : node.nodes_) {
            if (label) {
                label->accept(*this);
            }
        }
    }

    void visit(CaseLabelNode& node) override {
        if (node.expression_) {
            node.expression_->accept(*this);
        }
    }

    void visit(UnionForwardDclNode& node) override {
        // Default implementation does nothing
    }

    void visit(EnumDclNode& node) override {
        if (node.annotations_) {
            node.annotations_->accept(*this);
        }
        if (node.enumerators_) {
            node.enumerators_->accept(*this);
        }
    }

    void visit(ListNode<EnumeratorNode*>& node) override {
        for (auto& enumerator : node.nodes_) {
            if (enumerator) {
                enumerator->accept(*this);
            }
        }
    }

    void visit(EnumeratorNode& node) override {
        if (node.value_) {
            node.value_->accept(*this);
        }
    }

    void visit(TypeDefDclNode& node) override {
        node.refType_->accept(*this);
    }

    void visit(IncludeDclNode& node) override {
        // Default implementation does nothing
    }
};

#endif // defaultvisitor_h__
